import pika
from loguru import logger
import json

from configs import *


class JsonCustomEncoder(json.JSONEncoder):
    def default(self, obj):
        if isinstance(obj):
            # 处理自定义类型数据的编码逻辑
            return obj.to_json_serializable_format()
        return super().default(obj)

class MessageQueue:
    user = RABBITMQ['user']
    password = RABBITMQ['pass']
    port = RABBITMQ['port']
    host = RABBITMQ['host']
    vhost = RABBITMQ['vhost']
    exchange = Event_MQ['exchange']
    exchange_type = Event_MQ['exchange_type']
    routing_key = Event_MQ['routing_key']
    queue = Event_MQ['queue_name']
    arguments = Event_MQ['arguments']

    def __init__(self, queue_param=Event_MQ, rabbit_mq=RABBITMQ):
        """
        初始化队列参数
        :param queue_param: 队列参数
        :param rabbit_mq: RabbitMQ参数
        :return:
        """
        self.user = rabbit_mq['user']
        self.password = rabbit_mq['pass']
        self.host = rabbit_mq['host']
        self.vhost = rabbit_mq['vhost']
        self.port = rabbit_mq['port']
        self.exchange = queue_param['exchange']
        self.exchange_type = queue_param['exchange_type']
        self.routing_key = queue_param['routing_key']
        self.queue = queue_param['queue_name']
        self.arguments = queue_param['arguments']
        self.delay_time = queue_param.get('delay_time')

    @logger.catch
    def get_credentials(self):
        """
        获取队列认证信息
        :return:
        """
        return pika.PlainCredentials(self.user, self.password)

    @logger.catch
    def get_queue_parameter(self):
        """
        获取队列的链接参数
        :return:
        """
        return pika.ConnectionParameters(host=self.host,
                                         port=self.port,
                                         credentials=self.get_credentials(),
                                         virtual_host=self.vhost)

    @logger.catch
    def create_queue(self):
        """
        创建队列
        :return:
        """
        connection = pika.BlockingConnection(self.get_queue_parameter())
        channel = connection.channel()
        channel.exchange_declare(exchange=self.exchange,
                                 exchange_type=self.exchange_type,
                                 arguments=self.arguments,
                                 durable=True)
        channel.queue_declare(queue=self.queue, durable=True)
        channel.queue_bind(queue=self.queue,
                           exchange=self.exchange,
                           routing_key=self.routing_key)
        connection.close()

    def get_consumer_count(self):
        """
        获取队列的消费者数量
        @return: 当前在线的消费者数量
        """
        connection = pika.BlockingConnection(self.get_queue_parameter())
        channel = connection.channel()
        queue_state = channel.queue_declare(queue=self.queue, passive=True, durable=True)
        return queue_state.method.consumer_count

    @logger.catch
    def send_message(self, data: dict):
        """
        发送队列消息
        :param data: 消息内容，字典类型
        :return:
        """
        connection = pika.BlockingConnection(self.get_queue_parameter())
        channel = connection.channel()
        # headers = {'x-delay': time_delta * 1000}
        # properties = pika.BasicProperties(headers=headers)
        channel.basic_publish(exchange=self.exchange,
                              routing_key=self.routing_key,
                              body=json.dumps(data, cls=JsonCustomEncoder).encode())
        #                      properties=properties)
        connection.close()



